package cn.hacynn.nd.service.impl;

import cn.hacynn.nd.common.constant.MessageConstant;
import cn.hacynn.nd.common.context.BaseContext;
import cn.hacynn.nd.common.exception.FileException;
import cn.hacynn.nd.common.exception.TagException;
import cn.hacynn.nd.common.exception.TagFileException;
import cn.hacynn.nd.mapper.FileMapper;
import cn.hacynn.nd.mapper.TagFileMapper;
import cn.hacynn.nd.mapper.TagMapper;
import cn.hacynn.nd.pojo.dto.TagFileDTO;
import cn.hacynn.nd.pojo.dto.TagRenameDTO;
import cn.hacynn.nd.pojo.entity.File;
import cn.hacynn.nd.pojo.entity.Tag;
import cn.hacynn.nd.pojo.entity.TagFile;
import cn.hacynn.nd.service.FileService;
import cn.hacynn.nd.service.TagService;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.bind.annotation.PostMapping;

import java.text.SimpleDateFormat;
import java.util.List;
import java.util.TimeZone;

/**
 * @Author Hacynn
 * @Date 2024/5/27 14:44
 * @Version 1.0
 */
@Service
@Slf4j
public class TagServiceImpl implements TagService {

    @Autowired
    private TagMapper tagMapper;
    @Autowired
    private TagFileMapper tagFileMapper;
    @Autowired
    private FileMapper fileMapper;
    @Autowired
    private FileService fileService;


    /**
     * 获取所有tag标签
     * @return
     */
    @Override
    public List<Tag> getAllTags() {
        //获取当前用户信息
        Long userId = BaseContext.getCurrentId();
        //获取当前用户的所有文件夹
        return tagMapper.getByUserId(userId);
    }

    /**
     * 新增文件夹
     * @param name
     */
    @Override
    public void add(String name) {
        if (name == null) {
            // 标签名称为空
            throw new TagException(MessageConstant.TAG_NAME_IS_EMPTY);
        }
        // 判断标签是否已存在
        Tag tag = tagMapper.selectOne(new QueryWrapper<Tag>()
                .eq("name", name));
        if (tag != null) {
            // 该标签已存在
            throw new TagException(MessageConstant.TAG_EXISTS);
        }
        //获取当前用户信息
        Long userId = BaseContext.getCurrentId();
        //向tag中存入名称和当前用户
        tag = Tag.builder()
                .name(name)
                .userId(userId)
                .build();
        tagMapper.insert(tag);
    }

    /**
     * 获取属于该tag的所有文件
     * @param tagName
     * @return
     */
    @Override
    public List<File> getListByTag(String tagName) {
        //获取当前用户信息
        Long userId = BaseContext.getCurrentId();
        // 根据tagName获得tag对象
        Tag tag = tagMapper.selectOne(new QueryWrapper<Tag>()
                .eq("name", tagName)
                .eq("user_id", userId));
        if (tag == null) {
            // 标签不存在
            throw new TagException(MessageConstant.TAG_NOT_EXISTS);
        }
        // 获取属于该tag的所有文件id
        List<String> fileIds = tagFileMapper.geyByTagId(tag.getId());
        if (fileIds.isEmpty()) {
            // 标签下无文件
            throw new TagException(MessageConstant.TAG_NOT_FILE);
        }
        // 根据fileIds批处理获取所有文件信息
        List<File> files = fileMapper.selectBatchIds(fileIds);
        files.removeIf(f -> f.getInSafe() || f.getDeleted());  // 如果这个文件在保险箱里或者被放入了回收站，则从集合中删除，不显示
        // 根据是否为目录进行排序（目录排在前面）
        fileService.sortByDir(files);
        // 设置前端显示的最后修改时间
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("MM/dd HH:mm");
        simpleDateFormat.setTimeZone(TimeZone.getTimeZone("GMT+8"));
        files.forEach(f -> f.setLastModified(simpleDateFormat.format(f.getUpdateTime())));
        return files;
    }

    /**
     * 将文件添加指定的标签tag
     * @param tagFileDTO
     */
    @Override
    public void addFile(TagFileDTO tagFileDTO) {
        // 获得数据
        Long userId = BaseContext.getCurrentId();
        String tagName = tagFileDTO.getTagName();
        String ossPath = tagFileDTO.getOssPath();
        // 查询tag标签对象
        Tag tag = tagMapper.selectOne(new QueryWrapper<Tag>().eq("name", tagName));
        if (tag == null) {
            // 标签不存在
            throw new TagException(MessageConstant.TAG_NOT_EXISTS);
        }
        // 查询file文件对象
        File file = fileService.getFileByPath(userId, ossPath);
        if (file == null) {
            // 文件不存在
            throw new FileException(MessageConstant.FILE_NOT_EXIST);
        }
        // 判断该文件是否已存在该标签
        TagFile tagFile = tagFileMapper.selectOne(new QueryWrapper<TagFile>()
                .eq("file_id", file.getId())
                .eq("tag_id", tag.getId()));
        if (tagFile != null) {
            // 该标签下已存在该文件
            throw new TagFileException(MessageConstant.TAG_EXISTS_FILE);
        }
        // 更新对象
        tagFile = TagFile.builder()
                .fileId(file.getId())
                .tagId(tag.getId())
                .build();
        tagFileMapper.insert(tagFile);
    }

    /**
     * 将文件从指定的标签tag中移出
     * @param tagFileDTO
     */
    @Override
    public void moveFile(TagFileDTO tagFileDTO) {
        // 获得当前用户信息
        Long userId = BaseContext.getCurrentId();
        //获取当前要移除文件的名称和路径
        String tagName = tagFileDTO.getTagName();
        String ossPath = tagFileDTO.getOssPath();
        // 查询tag标签对象
        Tag tag = tagMapper.selectOne(new QueryWrapper<Tag>().eq("name", tagName));
        if (tag == null) {
            // 标签不存在
            throw new TagException(MessageConstant.TAG_NOT_EXISTS);
        }
        // 查询file文件对象
        File file = fileService.getFileByPath(userId, ossPath);
        if (file == null) {
            // 文件不存在
            throw new FileException(MessageConstant.FILE_NOT_EXIST);
        }
        // 判断该文件是否已存在该标签
        TagFile tagFile = tagFileMapper.selectOne(new QueryWrapper<TagFile>()
                .eq("file_id", file.getId())
                .eq("tag_id", tag.getId()));
        if (tagFile == null) {
            // 该标签下不存在该文件
            throw new TagFileException(MessageConstant.TAG_NOT_EXISTS_FILE);
        }
        //删除该文价夹
        tagFileMapper.deleteById(tagFile.getId());
    }

    /**
     * 删除标签
     * @param tagId
     */
    @Override
    public void delete(String tagId) {
        if (tagId == null) {
            // 标签id为空
            throw new TagException(MessageConstant.TAG_ID_IS_NULL);
        }
        //查询文件
        Tag tag = tagMapper.selectById(tagId);
        if (tag == null) {
            // 标签不存在
            throw new TagException(MessageConstant.TAG_NOT_EXISTS);
        }
        // 清除属于该标签的记录（不删除文件本身）
        // 先在tag_file删除
        tagFileMapper.deleteByTagId(tagId);
        // 在在tag删除文件夹
        tagMapper.deleteById(tagId);
    }

    /**
     * 标签重命名
     * @param tagRenameDTO
     */
    @Override
    public void rename(TagRenameDTO tagRenameDTO) {
        //获取要重命名文件夹的信息
        String tagId = tagRenameDTO.getTagId();
        String newName = tagRenameDTO.getNewName();
        //获取当前用户信息
        Long userId = BaseContext.getCurrentId();
        // 根据tagID查询出文件
        Tag tagDB1 = tagMapper.selectById(tagId);
        if (tagDB1 == null) {
            // 标签不存在
            throw new TagException(MessageConstant.TAG_NOT_EXISTS);
        }
        // 根据名称查询
        Tag tagDB2 = tagMapper.getByName(userId, newName);
        if (tagDB2 != null) {
            // 标签已存在，重新输入
            throw new TagException(MessageConstant.TAG_NAME_DUPLICATION);
        }
        // 更新数据库
        Tag tag = Tag.builder()
                .id(tagId)
                .name(newName)
                .build();
        tagMapper.updateById(tag);
    }



}
